package com.jxtc.enterprise.common.utils;

import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTVerifier;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.exceptions.JWTDecodeException;
import com.auth0.jwt.interfaces.DecodedJWT;
import com.jxtc.enterprise.admin.vo.adminEndpoint.AdminTenantDecryptdTokenVO;
import lombok.extern.slf4j.Slf4j;

import java.util.Date;

/**
 * @Author Scott
 * @Date 2018-07-12 14:23
 * @Desc JWT工具类
 **/
@Slf4j
public class JwtUtil {

	/**Token有效期为1小时（Token在reids中缓存时间为两倍）*/
	public static final long EXPIRE_TIME = 30L * 24 * 60 * 60 * 1000;
	public static final String JX_USER_LOGIN_PASSWORD = "jx_user_login_password";
	/**
	 * 校验token是否正确
	 *
	 * @param token  密钥
	 * @param secret 用户的密码
	 * @return 是否正确
	 */
	public static boolean verify(String token, String username, String secret) {
		try {
			// 根据密码生成JWT效验器
			Algorithm algorithm = Algorithm.HMAC256(secret);
			JWTVerifier verifier = JWT.require(algorithm).withClaim("username", username).build();
			// 效验TOKEN
			DecodedJWT jwt = verifier.verify(token);
			return true;
		} catch (Exception exception) {
			return false;
		}
	}

	public static DecodedJWT decodeJwtToken(String token, String username, String secret) {
		try {
			// 根据密码生成JWT效验器
			Algorithm algorithm = Algorithm.HMAC256(secret);
			JWTVerifier verifier = JWT.require(algorithm).withClaim("username", username).build();
			// 效验TOKEN
			DecodedJWT jwt = verifier.verify(token);
			return jwt;
		} catch (Exception exception) {
			log.error("{}", exception);
			return null;
		}
	}

	/**
	 * 获得token中的信息无需secret解密也能获得
	 *
	 * @return token中包含的用户名
	 */
	public static String getUsername(String token) {
		try {
			DecodedJWT jwt = JWT.decode(token);
			return jwt.getClaim("username").asString();
		} catch (JWTDecodeException e) {
			return null;
		}
	}

	/**
	 * 生成签名,5min后过期
	 *
	 * @param phoneNumber 用户名，待加密的明文
	 * @param secret   用户的密码，给明文加密时使用的密码，使用HMAC256加密算法对明文加密时，也需要提供一个密码；
	 * @return 加密的token
	 */
	public static String sign(String phoneNumber, String secret) {
		Date date = new Date(System.currentTimeMillis() + EXPIRE_TIME);
		Algorithm algorithm = Algorithm.HMAC256(secret);
		// 附带username信息
		return JWT.create().withClaim("phoneNumber", phoneNumber).withExpiresAt(date).sign(algorithm);
	}


	/**
	 * 从 token 中解码出 管理员或租户的身份信息
	 * @param token
	 * @return
	 */
	public static AdminTenantDecryptdTokenVO decryptPrincipalFromToken(String token) {
		try {
			DecodedJWT jwt = JWT.decode(token);

			String role = jwt.getClaim("role").asString();
			String userId = jwt.getClaim("userId").asString();
			String nickName = jwt.getClaim("nickName").asString();
			long expAt = jwt.getClaim("exp").asDate().getTime();

			AdminTenantDecryptdTokenVO adminTenantDecryptdTokenVO = new AdminTenantDecryptdTokenVO();
			adminTenantDecryptdTokenVO.setRole(role);
			adminTenantDecryptdTokenVO.setUserId(userId);
			adminTenantDecryptdTokenVO.setExpAt(expAt);

			return adminTenantDecryptdTokenVO;
		} catch (JWTDecodeException e) {
			log.error("token 解码失败，无效的token");
			return new AdminTenantDecryptdTokenVO("unknown-role", "unknown-userid", 0);
		}
	}


//	public static void main(String[] args) {
//		 String token = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1NjUzMzY1MTMsInVzZXJuYW1lIjoiYWRtaW4ifQ.xjhud_tWCNYBOg_aRlMgOdlZoWFFKB_givNElHNw3X0";
//		 System.out.println(JwtUtil.getUsername(token));
//	}
}
